package com.mustafaiev.tair.cts.dao.jpa;

import java.util.List;

import org.apache.log4j.Logger;
import org.hibernate.HibernateException;
import org.hibernate.Query;
import org.hibernate.Session;
import org.hibernate.Transaction;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.orm.hibernate3.HibernateTemplate;
import org.springframework.stereotype.Repository;
import org.springframework.transaction.annotation.Transactional;

import com.mustafaiev.tair.cts.dao.IBasketsBatchDAO;
import com.mustafaiev.tair.cts.exeption.DataNotRemovedException;
import com.mustafaiev.tair.cts.exeption.DataNotStoredException;
import com.mustafaiev.tair.cts.model.Basket;
import com.mustafaiev.tair.cts.model.BasketsBatch;
import com.mustafaiev.tair.cts.model.BasketsBatchFilter;

@Repository(value = "basketsBatchDao")
@Transactional
public class BasketsBatchDAO implements IBasketsBatchDAO {

	private static final String UPDATE_BATCH_FOR_BASKETS = "update Basket set basketsBatchId = null where basketsBatchId = ?";

	private static final String SELECT_ALL_FROM_BASKETS_BATCH = "from BasketsBatch";

	private static final Logger LOGGER = Logger
			.getLogger(BasketsBatchDAO.class);

	private HibernateTemplate hibernateTemplate;

	@Autowired
	public void setHibernateTemplate(final HibernateTemplate hibernateTemplate) {
		this.hibernateTemplate = hibernateTemplate;
	}

	@Override
	public void doSave(final BasketsBatch t) throws DataNotStoredException {
		final Session session = this.hibernateTemplate.getSessionFactory()
				.openSession();
		final Transaction transaction = session.getTransaction();
		try {
			transaction.begin();
			session.saveOrUpdate(t);
			final List<Basket> baskets = t.getBaskets();
			for (final Basket basket : baskets) {
				basket.setBasketsBatch(t);
				session.saveOrUpdate(basket);
			}
			transaction.commit();
		} catch (final HibernateException e) {
			LOGGER.error(e);
			throw new DataNotStoredException(
					"Baskets batch was not stored for a some reason", e);
		}
	}

	@Override
	public void doDeleteById(final Long id) throws DataNotRemovedException {

	}

	@Override
	public void doDelete(final BasketsBatch t) throws DataNotRemovedException {
		final Session session = this.hibernateTemplate.getSessionFactory()
				.openSession();
		final Transaction transaction = session.getTransaction();
		try {
			transaction.begin();
			final Query query = session.createQuery(UPDATE_BATCH_FOR_BASKETS)
					.setLong(0, t.getId());
			query.executeUpdate();
			session.delete(t);
			transaction.commit();
		} catch (final HibernateException e) {
			LOGGER.error(e);
			throw new DataNotRemovedException(
					"Baskets batch was not removed for a some reason", e);
		}
	}

	@SuppressWarnings("unchecked")
	@Override
	public List<BasketsBatch> retreiveBatches() {
		final Session session = this.hibernateTemplate.getSessionFactory()
				.openSession();
		List<BasketsBatch> batches = null;
		try {
			batches = session.createQuery(SELECT_ALL_FROM_BASKETS_BATCH).list();
		} catch (final HibernateException e) {
			LOGGER.error(e);
		}
		return batches;
	}

	@Override
	public BasketsBatch retrieveBatch(final Long batchId) {
		final Session session = this.hibernateTemplate.getSessionFactory()
				.openSession();
		BasketsBatch basketsBatch = null;
		try {
			basketsBatch = (BasketsBatch) session.get(BasketsBatch.class,
					batchId);
		} catch (final HibernateException e) {
			LOGGER.error(e);
		}
		return basketsBatch;
	}

	@Override
	public List<BasketsBatch> retrieveBatchesByFilter(
			final BasketsBatchFilter filter) {
		return null;
	}

	@Override
	public void doUpdate(final BasketsBatch t) throws DataNotStoredException {

	}

}
